// @document https://developer.atlassian.com/cloud/jira/platform/rest/v2/intro/#about
// depend RequestJs.js
// depend LocalString.js
// depend Debug.js
class JiraClient
{
    constructor(options)
    {
        if (Object.keys(options).length) {
            this.init(options);
        }
    }

    init(options)
    {
        if (options.token) {
            this.token = options.token;
        }
        if (options.host) {
            this.host = options.host;
        }
        if (options.headers) {
            this.headers = options.headers;
        }
        return this;
    }

    getUrl(uri)
    {
        return this.host + uri;
    }

    request(url, params)
    {
        if (!params) {
            params = {};
        }

        if (this.token) {
            if (this.headers) {
                this.headers.token = this.token;
                params.headers = this.headers;
            } else {
                if (!params.headers) {
                    params.headers = {};
                }
                params.headers.token = this.token;
            }
        }

        let requestJs = new RequestJS();
        return requestJs.fetch(url, params);
    }

    getIssue(issueKeyOrId)
    {
        return this.request(this.getUrl('/rest/api/2/issue/' + issueKeyOrId));
    }

    updateIssue(issueKeyOrId, data)
    {
        return this.request(this.getUrl('/rest/api/2/issue/' + issueKeyOrId), {
            method: 'PUT',
            raw: JSON.stringify(data)
        });
    }

    createIssue(issueObject)
    {
        return this.request(this.getUrl('/rest/api/2/issue'), {
            method: 'POST',
            raw: JSON.stringify(issueObject)
        })
    }

    createLink(mainIssueKey, childIssueKey, linkType)
    {
        if (!linkType) {
            // Contains
            linkType = 'Hierarchy link (WBSGantt)';
        }
        let linkJson = {
            outwardIssue: {
                key: childIssueKey
            },
            inwardIssue: {
                key: mainIssueKey
            },
            type: {
                name: linkType
            }
        };
        return this.request(this.getUrl('/rest/api/2/issueLink'), {
            method: 'POST',
            raw: JSON.stringify(linkJson)
        })
    }

    setTransition(issueKeyOrId, transitionId)
    {
        return this.request(this.getUrl('/rest/api/2/issue/' + issueKeyOrId + '/transitions'), {
            method: 'POST',
            raw: JSON.stringify({
                transition:{
                    id: transitionId
                }
            })
        });
    }

    getTransition(issueKeyOrId)
    {
        return this.request(this.getUrl('/rest/api/2/issue/' + issueKeyOrId + '/transitions'));
    }

    search(jql, options)
    {
        // if url is localhost
        let preg = new RegExp(/localhost/);
        let isLocal = preg.test(this.getUrl('/'));
        if (isLocal) {
            jql = {'jql':jql};
            if (options) {
                if (options.start) {
                    jql.startAt = options.start;
                }
                if (options.size) {
                    jql.maxResults = options.size;
                }
            }
            return this.request(this.getUrl('/rest/api/2/search'), {
                method: 'POST',
                raw: JSON.stringify(jql)
            });
        } else {
            if (options) {
                if (options.start) {
                    jql += '&startAt=' + options.start;
                }
                if (options.size) {
                    jql += '&maxResults=' + options.size;
                }
            }
            return this.request(this.getUrl('/rest/api/2/search?jql=' + jql));
        }
    }

    addComment(issueKeyOrId, content)
    {
        return this.request(this.getUrl('/rest/api/2/issue/' + issueKeyOrId + '/comment'), {
            method: 'POST',
            raw: JSON.stringify({
                body:content
            })
        });
    }
}
